package net.cohoivang.core;

import java.util.LinkedList;
import java.util.List;

import net.cohoivang.news.EnableToTopListener;
import net.cohoivang.news.ExpireListener;
import net.cohoivang.news.INews;
import net.cohoivang.news.News;
import net.cohoivang.web.GoldenChance;

public class TradingThread extends Thread{
	private static TradingThread instance;
	private final LinkedList<INews> tradingNewss = new LinkedList<INews>();	
	
	private boolean shutdownRequest = false;
	
	private int interval;
	
	public static TradingThread getInstance() {
		return instance;
	}
	
	public static void initialize() {
		instance = new TradingThread();
		instance.loadAvaibleTradingNews();
	}
	
	private TradingThread() {
		super("trading news thread");
		try {
			interval = Integer.parseInt(GoldenChance.getProperties("intervalTradingNews"));
		} catch (NumberFormatException ex) {
			interval = 1000;
		}
		start();
	}
	
	private void loadAvaibleTradingNews() {
		System.out.println("load available trading news");
		List<Company> companyList = ProfileCompany.getInstance().getAllCompany();
		int count = 0;
		for (Company company : companyList) {
			for (News news : company.getAllNews()) {
				if (news.isAvailable()) {
					addNews(news);
					count ++;
				}
			}
		}
		System.out.println("Total " + count + "available trading news is loaded");
	}
	
	
	
	public void shutdown() {
		synchronized (tradingNewss) {
			shutdownRequest = true;
			System.out.println("Trading thread shutdown request ...");
			tradingNewss.notifyAll();
		}
	}
	
	public void addNews(INews news) {
		synchronized (tradingNewss) {
			tradingNewss.add(news);
			tradingNewss.notifyAll();
		}
	}	
	
	public void run() {
		while (true) {
			if (!runSafe()) {
				break;
			}
		}
	}
	
	private boolean runSafe() {
		synchronized (tradingNewss) {
			if (tradingNewss.isEmpty()) {
				if (shutdownRequest) {
					System.out.println("shutdown trading thread");
					return false;
				}
				try {
					tradingNewss.wait();
				} catch (InterruptedException ex) {
					ex.printStackTrace();
				}
			}
			
			for (INews in : tradingNewss) {
				int currentTime = in.processExpireTime(interval);
				if (currentTime == 0) {
					tradingNewss.remove(in);
					if (in.isTop()) {
						LinkedList<EnableToTopListener> etList = in.getEnableToTopListListeners();
						for (EnableToTopListener et : etList) {
							et.disableFromTop(in);
							//et.disableFromTop(et);
						}
					}
				}
			}		
		}
		try {
			Thread.sleep(interval);
		} catch (InterruptedException ex) {
			ex.printStackTrace();
		}
		return true;
	}
}
